import { Loger } from "../loger/Loger";

export class LinkNode<T>{
    public data: T;
    public next: LinkNode<T>;
    constructor(data: T) {
        this.data = data;
        this.next = null;
    }
}

export class LinkList<T>{
    private _head: LinkNode<T>;
    private length: number;
    private _tail: LinkNode<T>;
    public get head(): LinkNode<T> { return this._head }
    public get tail(): LinkNode<T> { return this._tail }
    constructor() {
        this._head = null;
        this._tail = null;
        this.length = 0;
    }

    append(data: T): boolean {
        let new_node = new LinkNode(data);
        if (this._head == null) {
            this._head = new_node
            this._tail = new_node;
        } else {
            this._tail.next = new_node;
            this._tail = this._tail.next;
        }
        this.length++;
        return true;
    }

    len(): number {
        return this.length;
    }

    insert(index: number, data: T): boolean {
        if (index == this.length) {
            return this.append(data);
        } else {
            let insert_index = 1;
            let cur_node = this._head;
            while (insert_index < index) {
                cur_node = cur_node.next;
                insert_index++;
            }
            let next_node = cur_node.next;
            let new_node = new LinkNode(data);
            cur_node.next = new_node;
            cur_node.next.next = next_node;
        }
        this.length++;
        return true;
    }

    remove(index): LinkNode<T> {
        if (index < 0 || index >= this.length) {
            return null;
        } else {
            let del_node = null;
            if (index == 0) {
                del_node = this._head;
                this._head = this._head.next;
            } else {
                let del_index = 0;
                let pre_node = null;
                let cur_node = this._head;
                while (del_index < index) {
                    del_index++;
                    cur_node = cur_node.next;
                }
                pre_node = cur_node;
                cur_node = cur_node.next;
                pre_node.next = cur_node;
                //如果删除的是尾节点
                if (cur_node == null) {
                    this._tail = pre_node;
                }
                this.length--;
                return del_node;
            }
        }
    }

    get(index): LinkNode<T> {
        if (index < 0 || index > this.length) {
            return null;
        }
        let node_index = 0;
        let cur_node = this._head;
        while (node_index < index) {
            node_index++;
            cur_node = cur_node.next;
        }
        return cur_node;
    }

    print(): void {
        let cur = this._head;
        while (cur != null) {
            Loger.log(cur.data);
            cur = cur.next;
        }
    }

}